home *** CD-ROM | disk | FTP | other *** search
Text File | 2000-09-28 | 19.3 KB | 707 lines | [TEXT/MPS ] |
- /*
- File: FontDBasePrerequisites.c
-
- Contains: QuickDraw GX to PostScript conversion code.
- File contains code to handle prerequisites for the fonts
- in the font database.
-
- Version: Technology: Quickdraw GX 1.1.x
-
- Copyright: © 1991-1997 by Apple Computer, Inc., all rights reserved.
- */
-
-
- // allow multiple references to single label
- #define resumeLabel(exception)
- #include <MacMemory.h>
- #include <Resources.h>
- #include "GXExceptions.h"
- #include "GXPrintingUniverse.h"
- #include "IOUtilities.h"
-
- #include <GXFonts.h>
-
-
- //#include <OFA1TypesPriv.h>
-
- #ifndef __COLLECTIONMANAGER__
- #include <Collections.h>
- #endif
-
- #ifndef __FONTDBASEHANDLER__
- #include "FontDatabase.h"
- #endif
-
- #include "FontDBasePrivate.h"
-
- typedef struct {
- gxSpoolBlock spool;
-
- Handle streamHdl;
- long count;
- long size;
- OSErr saveError;
-
- } userSpool;
-
-
- static long FDBSpoolProc(gxSpoolCommand command, struct gxSpoolBlock *block)
- {
- #pragma unused (command, block)
-
- /** do nothing **/
-
- return(0);
- }
-
-
- /***********************************
- Function: FDBStreamFont:
-
- Function is a wrapper for stream font.
- If messaging is indicated, the message is sent.
- If not, GXFlattenFont is called directly.
-
- *************************************/
- OSErr FDBStreamFont(gxFont theFont, scalerStream *pStreamRecord);
- OSErr FDBStreamFont(gxFont theFont, scalerStream *pStreamRecord)
- {
- OSErr status;
- gxSpoolBlock dummyBlock;
- unsigned char dummyBuffer;
-
-
- #if GENERATINGPOWERPC
- RoutineDescriptor fdbSpoolProc_RD = BUILD_ROUTINE_DESCRIPTOR(uppgxSpoolProcInfo, FDBSpoolProc);
- gxSpoolUPP fdbSpoolProc_UPP = (gxSpoolUPP) &fdbSpoolProc_RD;
- #else
- gxSpoolUPP fdbSpoolProc_UPP = (gxSpoolUPP) FDBSpoolProc;
- #endif
-
- dummyBlock.buffer = &dummyBuffer;
- dummyBlock.bufferSize = 1;
- dummyBlock.spoolProcedure = fdbSpoolProc_UPP;
- GXFlattenFont(theFont, pStreamRecord, &dummyBlock);
-
- status = GXGetGraphicsError(nil);
-
-
- ncheck(status);
- return(status);
-
- }//FDBStreamFont
-
-
-
- //<FF>
- /*****************************************
-
- Routine turns on and off inclusion of prerequisite
- data for a font in the database.
-
- fontDbase: the font database.
- theFont: The font to set it for.
- exclude: false for include, true for exclude.
-
- *******************************************/
- OSErr FontDbaseExcludePrerequisite(TFontDbase fontDbase, gxFont theFont, Boolean exclude)
- {
- OSErr status;
- TfdbInfoFlags fontFlags; // font's flags.
-
- /*** Get the font's flags ****/
-
- status = FontDbaseGetFontInfo(fontDbase, theFont, nil, nil, nil, &fontFlags);
- nrequire(status, failed_GetInfo);
-
- /** Set or clear the prerequisite exclusion bit as indicated **/
-
- if (exclude)
- fontFlags |= fdbExcludeFontPrereqs;
- else
- fontFlags &= ~fdbExcludeFontPrereqs;
-
- /** Now set the flags back in the font **/
-
- status = FontDbaseSetFontFlags(fontDbase, theFont, fontFlags);
- nrequire(status, failed_SetFlags);
-
- failed_SetFlags:
- failed_GetInfo:
-
- return(status);
-
- }//_FontDbaseExcludePrerequisite
-
-
- //<FF>
- /**************************************
-
- Function: FDBUnionPrerequisiteList
-
- This function unions in a new prerequisite list
- with the prerequisite collection.
-
- hDbase: the handle to the font database.
- theFont: The font reference that was used to obtain the list.
- listSize: size in bytes of the new list.
- list: pointer to the list data.
-
-
- ****************************************/
- OSErr FDBUnionPrerequisiteList(TFontDbaseHdl hDbase, gxFont theFont, long listSize, unsigned char *list, long *count);
- OSErr FDBUnionPrerequisiteList(TFontDbaseHdl hDbase, gxFont theFont, long listSize, unsigned char *list, long *count)
- {
- OSErr status;
- unsigned char *inList; // Point into the list;
- unsigned char *endList; // Pointer to end of list;
- gxFontFormatTag fontFormat; // Get the font format.
- scalerPrerequisiteItem *item; // Pointer to the item.
- Collection prerequisites; // the prerequisite collection.
- long enumeration;
- long itemSize;
-
- fontFormat = GXGetFontFormat(theFont);
-
- inList = list;
- endList = list + listSize;
-
- prerequisites = (*hDbase)->prerequisites;
-
- /*** Walk the list and add items to the collection as appropriate ***/
-
- while (inList < endList) {
-
- item = (scalerPrerequisiteItem*)inList;
-
- /** compute size of item add the name length to the structure size. **/
-
- itemSize = 8 + item->name[0] + 1; /** structure is two longs followd by a pascal string if it changes we die **/
-
- /** See if the item is already in the collection **/
-
- enumeration = item->enumeration;
- status = GetCollectionItem(prerequisites, (CollectionTag)fontFormat, enumeration, nil, nil);
-
- /** If the item was not found, add it to the collection **/
-
- if (status == collectionItemNotFoundErr) {
-
- /*****
- replace the enumeration in the structure with the font reference (a handy place to stick it)
- since we need the reference somewhere and we are already using the enumeration as the
- collection item ID
- ******/
- item->enumeration = (long)theFont;
-
- status = AddCollectionItem(prerequisites, (CollectionTag)fontFormat, enumeration, itemSize, item);
- nrequire(status, failed_AddItem);
-
- *count += 1; // Increment the count of how many prerequisites.
-
- } else if (status != noErr) {
-
- /** some other error happened, get out of loop **/
-
- ncheck(status);
- break;
-
- }//end if
-
- /** Point to the next item in the list **/
-
- inList += itemSize;
-
- }//end while
-
-
- failed_AddItem:
-
- return(status);
-
- }//FDBUnionPrerequisiteList
-
- //<FF>
- /*************************************
-
- Function: FontDbaseBuildPrerequisiteList
-
- Function builds the internal list of the prerequisites
- required for the set of document fonts. This function can
- be called over and over again with different stream types or
- when new fonts have been added to the database.
- Each time, the old list is tossed and a new one created.
-
- fontDbase: the font database object.
- streamTypes: The stream types for which to build the prerequisite list.
- useMessage: Indicates whether the stream call should go through the PostScript message.
- (should only be true at Imaging time when stream types are for PS)
- count: returned: Number of prerequisite items in the list.
-
- **************************************/
-
- OSErr FontDbaseBuildPrerequisiteList(TFontDbase fontDbase, scalerStreamTypeFlag streamTypes,
- char *productDescription, Boolean useMessages, long *count)
- {
- OSErr status;
- TFontDbasePtr pDbase;
- Handle hList; // Use for scratch memory to get list from scaler.
- long scratchSize; // size of scratch handle.
- long nFonts;
- long idx;
- gxFont theFont;
- scalerStream streamRecord;
- TfdbInfoFlags fontFlags;
-
- *count = 0;
- pDbase = *(TFontDbaseHdl)fontDbase;
-
- /* If there was alread a list, throw it away - we'll build a new one */
-
- if (pDbase->prerequisites != nil)
- DisposeCollection(pDbase->prerequisites);
-
- /* Make a new collection for the prerequisite list */
-
- pDbase = *(TFontDbaseHdl)fontDbase;
- pDbase->prerequisites = NewCollection();
- pDbase = *(TFontDbaseHdl)fontDbase; // in case memory moved.
- require_action(pDbase->prerequisites, failed_NewCollection, status = MemError(););
-
-
- pDbase->streamTypes = streamTypes; // Value passed in becomes current value for subsequent actions.
-
- /** Allocate a scratch handle for retrieving prerequisite lists **/
-
- status = PrNewHandle(&hList, 0);
- nrequire(status, failed_AllocScratch);
- scratchSize = 0;
-
-
- /********
- Loop through all of the fonts in the database.
- Get their prerequisite list
- Union it into the collection.
- *********/
- pDbase = *(TFontDbaseHdl)fontDbase; // in case memory moved.
- nFonts = pDbase->numFonts;
- for (idx = 1; idx <= nFonts; ++idx) {
-
- status = FontDbaseGetIndexedFont(fontDbase, idx, &theFont);
- nrequire(status, failed_GetFont);
-
- /** See if we should include data for this font in the prerquisite list **/
-
- status = FontDbaseGetFontInfo(fontDbase, theFont, nil, nil, nil, &fontFlags);
- nrequire(status, failed_GetInfo);
-
- /* For fonts whose prerequisites we don't exclude */
-
- if ( !(fontFlags & fdbExcludeFontPrereqs) ) {
-
- /** Get the size of the list **/
-
- streamRecord.types = streamTypes;
- streamRecord.targetVersion = productDescription;
- streamRecord.action = prerequisiteQueryStreamAction;
- streamRecord.variationCount = selectAllVariations;
- streamRecord.variations = nil;
- streamRecord.info.prerequisiteQuery.list = nil;
- status = FDBStreamFont(theFont, &streamRecord);
- nrequire(status, failed_sizeQuery);
-
- /* If the list size was not zero, there are prerequisites */
-
- if ( streamRecord.info.prerequisiteQuery.size > 0 ) {
-
- /** Size the scratch space accordingly to retrieve list **/
-
- if ( streamRecord.info.prerequisiteQuery.size > scratchSize ) {
-
- scratchSize = streamRecord.info.prerequisiteQuery.size;
- status = PrSetHandleSize(hList, scratchSize);
- nrequire(status, failed_resizeScratch);
-
- }//end if
-
- /** Get the list itself **/
-
- HLock(hList);
- streamRecord.info.prerequisiteQuery.list = *hList;
- status = FDBStreamFont(theFont, &streamRecord);
- nrequire(status, failed_GetList);
-
- /** Now union the list into the current collection **/
-
- status = FDBUnionPrerequisiteList((TFontDbaseHdl)fontDbase, theFont, streamRecord.info.prerequisiteQuery.size,
- (unsigned char*)*hList, count);
- nrequire(status, failed_Union);
-
- HUnlock(hList);
-
- }//end if
-
- }//end if
-
- }//end for
-
- failed_Union:
- failed_GetList:
- failed_resizeScratch:
- failed_sizeQuery:
- failed_GetInfo:
- failed_GetFont:
-
- /* Clean up allocations */
-
- DisposeHandle(hList);
-
- failed_AllocScratch:
-
- /* Clean up if an error happend */
-
- if (status != noErr) {
-
- pDbase = *(TFontDbaseHdl)fontDbase;
- DisposeCollection(pDbase->prerequisites);
- pDbase->prerequisites = nil;
-
- }//end if
-
- failed_NewCollection:
-
- return(status);
-
- }//FontDbaseBuildPrerequisiteList
-
-
-
-
-
- /*********************************************
-
- Function: FontDbaseGetIndexedPrerequisite
-
- Function returns information on the prerequisite in the list
- based on index passed in.
-
- fontDbase: the font database object.
- idx: the index of the desired prerequisite.
- size: (returned). Size of item.
- theFont: (returned). Font reference to use with this prerequisite.
- Must pass nil if nil is passed for item
- item: The prerequisite item is filled in here.
- **********************************************/
- OSErr FontDbaseGetIndexedPrerequisite(TFontDbase fontDbase, long idx, long *size, gxFont *theFont, scalerPrerequisiteItem *item)
- {
- OSErr status;
- Collection prerequisites;
- long enumeration;
-
- prerequisites = (*(TFontDbaseHdl)fontDbase)->prerequisites;
- require_action(prerequisites, failed_DontHaveCollection, if (size) *size = 0;);
-
- status = GetIndexedCollectionItem(prerequisites, idx, size, item);
- nrequire(status, failed_GetItem);
-
- /*****
- Since the font reference was stored in the item in place of the enumeration
- and the enumeration is stored in the collection item's id, retrieve and
- repair.
- ******/
- if ( item != nil ) {
-
- status = GetIndexedCollectionItemInfo(prerequisites, idx, nil, &enumeration, nil, nil);
- nrequire(status, failed_GetInfo);
-
- if (theFont != nil)
- *theFont = (gxFont)item->enumeration; // we hid the font reference in here, hey it's a long too.
-
- item->enumeration = enumeration; // Put the real enumeration in here.
-
- }//end if
-
- failed_GetInfo:
- failed_GetItem:
- failed_DontHaveCollection:
- return(status);
-
- }//FontDbaseGetIndexedPrerequisite
-
- //<FF>
-
- static long FDBPartialSpoolProc(gxSpoolCommand command, userSpool *block)
- {
- OSErr status = noErr;
-
- switch (command)
- {
- case gxOpenReadSpool:
- #if DEBUGLEVEL>0
- DebugStr("\pinvalid open read request in FDBPartialSpoolProc" );
- #endif
- break;
- case gxOpenWriteSpool:
- if( block->size > 0 )
- {
- block->count = 0;
- SetResourceSize( block->streamHdl, block->size );
- nrequire( status = ResError(), failed_SetResourceSize );
- }
- break;
- case gxReadSpool:
- #if DEBUGLEVEL>0
- DebugStr("\pinvalid read request in FDBPartialSpoolProc" );
- #endif
- break;
- case gxWriteSpool:
- check( ( block->count + block->spool.count ) <= block->size );
- WritePartialResource( block->streamHdl, block->count, block->spool.buffer, block->spool.count );
- nrequire( status = ResError(), failed_WritePartialResource );
- block->count += block->spool.count;
- break;
- case gxCloseSpool:
- check( block->size == 0 || ( GetResourceSizeOnDisk( block->streamHdl ) == block->size ) );
- break;
- }
-
- failed_SetResourceSize:
- failed_WritePartialResource:
-
- if (!block->saveError) block->saveError = status;
-
- return(status);
- }
-
-
- //<FF>
- /*************************************************
-
- Function: FDBFontToHandle
-
- Function flattens a font into a handle.
-
- **************************************************/
- OSErr FDBFontToHandle(gxFont fontID, long glyphBits[], Handle h)
- {
- userSpool block;
- scalerStream stream;
- OSErr status;
- Handle hBuffer;
-
- #if GENERATINGPOWERPC
- RoutineDescriptor fdbPartialSpoolProc_RD = BUILD_ROUTINE_DESCRIPTOR(uppgxSpoolProcInfo, FDBPartialSpoolProc);
- gxSpoolUPP fdbPartialSpoolProc_UPP = (gxSpoolUPP) &fdbPartialSpoolProc_RD;
- #else
- gxSpoolUPP fdbPartialSpoolProc_UPP = (gxSpoolUPP) FDBPartialSpoolProc;
- #endif
-
- check (h);
-
- block.streamHdl = h;
- block.count = 0;
- block.size = 0;
- block.saveError = noErr;
-
- #define flatBufferSize 4096
-
- nrequire( status = PrNewHandle( &hBuffer, flatBufferSize ), NewBufferFailed );
-
- HLock( hBuffer ); block.spool.buffer = *hBuffer;
-
- block.spool.bufferSize = flatBufferSize;
-
- #undef flatBufferSize
-
- block.spool.spoolProcedure = fdbPartialSpoolProc_UPP;
-
- stream.streamRefCon = fontID;
- stream.types = flattenedStreamType;
- stream.action = fontSizeQueryStreamAction;
- stream.memorySize = 0;
- stream.variationCount = selectAllVariations;
- stream.variations = nil;
- stream.info.font.encoding = nil;
- stream.info.font.glyphBits = glyphBits;
- stream.info.font.name = nil;
-
- GXFlattenFont(fontID, &stream, &block.spool);
-
- status = GXGetGraphicsError(nil);
- nrequire(status, failed_flatten);
-
- check( stream.memorySize > 0 );
-
- block.size = stream.memorySize;
- stream.action = downloadStreamAction;
-
- GXFlattenFont(fontID, &stream, &block.spool);
-
- status = GXGetGraphicsError(nil);
- nrequire(status, failed_flatten);
-
- failed_flatten:
- HUnlock( hBuffer );
- NewBufferFailed:
- DisposeHandle( hBuffer );
-
- if (block.saveError != noErr) /* Get the error that we generated in our spool proc */
- status = block.saveError;
-
- return(status);
-
- }//FDBPrereqToHandle
-
-
- /*************************************************
-
- Function: FDBPrereqToHandle
-
- Function flattens a prerequisite item into a handle.
-
- **************************************************/
- OSErr FDBPrereqToHandle(gxFont fontID, scalerPrerequisiteItem *item, Handle h)
- {
- userSpool block;
- scalerStream stream;
- OSErr status;
- Handle hBuffer;
-
- #if GENERATINGPOWERPC
- RoutineDescriptor fdbPartialSpoolProc_RD = BUILD_ROUTINE_DESCRIPTOR(uppgxSpoolProcInfo, FDBPartialSpoolProc);
- gxSpoolUPP fdbPartialSpoolProc_UPP = (gxSpoolUPP) &fdbPartialSpoolProc_RD;
- #else
- gxSpoolUPP fdbPartialSpoolProc_UPP = (gxSpoolUPP) FDBPartialSpoolProc;
- #endif
-
- check (h);
- check( item->size > 0 );
- block.streamHdl = h;
- block.size = item->size;
- block.count = 0;
- block.saveError = noErr;
-
- #define flatBufferSize 512
-
- nrequire( status = PrNewHandle( &hBuffer, flatBufferSize ), NewBufferFailed );
-
- HLock( hBuffer ); block.spool.buffer = *hBuffer;
-
- block.spool.bufferSize = flatBufferSize;
-
- #undef flatBufferSize
-
- block.spool.spoolProcedure = fdbPartialSpoolProc_UPP;
-
- stream.streamRefCon = fontID;
- stream.types = flattenedStreamType;
- stream.action = prerequisiteItemStreamAction;
- stream.memorySize = 0;
- stream.variationCount = selectAllVariations;
- stream.variations = nil;
- stream.info.prerequisiteItem = item->enumeration;
-
- GXFlattenFont(fontID, &stream, &block.spool);
-
- status = GXGetGraphicsError(nil);
- nrequire(status, failed_flatten);
-
- failed_flatten:
- HUnlock( hBuffer );
- NewBufferFailed:
- DisposeHandle( hBuffer );
-
- if (block.saveError != noErr) /* Get the error that we generated in our spool proc */
- status = block.saveError;
-
- return(status);
-
- }//FDBPrereqToHandle
-
-
- #if !GXTOPOSTSCRIPTLIBRARY
- /*-----------------------------------------------------------------------------------
-
- CreatePartialStreamTempFile
-
- this routines creates a file into which we can stream a partial font
-
- -----------------------------------------------------------------------------------*/
- OSErr CreatePartialStreamTempFile( TFile *filerefPtr, Handle *streamHdlPtr )
- {
- OSErr status;
-
- TFile fileref = nil;
- Handle streamHdl = nil;
- FSSpec spec;
-
- nrequire( status = FindFolder( kOnSystemDisk, kTemporaryFolderType, kCreateFolder,
- & spec.vRefNum, & spec.parID ), FindTempFolderFailed );
-
- /* the following string does not need to be localized so it is ok to leave it as is */
-
- #define TempStreamFileName "\pGX Printing Temp"
-
- check( sizeof( TempStreamFileName ) < 32 );
-
- BlockMove( TempStreamFileName, spec.name, sizeof( TempStreamFileName ) );
-
- #undef TempStreamFileName
-
- nrequire( status = FHNewFileReference( &fileref ), NewFileRefFailed );
- nrequire( status = FHCreateFile( fileref, &spec, true ), CreateFileFailed );
-
- // creating the file also opens it -- how weird
-
- nrequire( status = PrNewHandle( &streamHdl, 0 ), NewHandleFailed );
-
- nrequire( status = FHAddResource( fileref, streamHdl, 'TEMP', 128 ), AddResourceFailed );
- SetResAttrs( streamHdl, resPurgeable );
- WriteResource( streamHdl ); nrequire( status = ResError(), WriteResourceFailed );
-
- HPurge( streamHdl );
- EmptyHandle( streamHdl ); /* purge the handle */
-
- check( *streamHdl == nil ); /* check that it has been purged */
-
- *streamHdlPtr = streamHdl;
- *filerefPtr = fileref;
-
- return( noErr );
-
- AddResourceFailed:
- (void) PrDisposeHandle( streamHdl );
- GetPurgeHandleFailed:
- WriteResourceFailed: ReleaseStreamFailed: NewHandleFailed:
- OpenFileFailed:
- (void) FHCloseFile( fileref, false );
- CreateFileFailed:
- (void) FHDeleteFile( fileref );
-
- NewFileRefFailed:
- FindTempFolderFailed:
- return( status );
- }
-
- /*-----------------------------------------------------------------------------------
-
- DisposePartialStreamTempFile
-
- this routine gets rid of the file that we created above
-
- -----------------------------------------------------------------------------------*/
- void DisposePartialStreamTempFile( TFile fileref, Handle streamHdl )
- {
- check( fileref );
- check( streamHdl );
- check( *streamHdl == nil );
-
- (void) FHReleaseResource( fileref, streamHdl );
-
- // somehow you can only delete an opened file -- how weird
- (void) FHDeleteFile( fileref );
- (void) FHDisposeFileReference( fileref );
- }
-
- #endif
-